package com.dev.toolkit.common.util;

import cn.hutool.core.collection.CollectionUtil;
import com.dev.toolkit.domain.bo.EntityPropertyConfigBO;
import com.dev.toolkit.domain.bo.GenerateCodeConfigBO;
import com.github.javaparser.ast.CompilationUnit;
import com.github.javaparser.ast.Modifier;
import com.github.javaparser.ast.body.ClassOrInterfaceDeclaration;
import com.github.javaparser.ast.body.FieldDeclaration;
import com.github.javaparser.ast.comments.JavadocComment;

import java.util.List;

/**
 * @author ZhuYouBin
 * @version 1.0.0
 * @date 2024/4/26 17:06
 * @description Java代码生成工具类
 */
public class JavaCodeGenerateUtil {
    private static final String PACKAGE_NAME = "com.code";
    private static final String CLASS_NAME = "Main";

    public static String generateJavaClass(GenerateCodeConfigBO config) {
        // 创建编译对象
        CompilationUnit cu = new CompilationUnit();
        // 设置包路径
        cu.setPackageDeclaration(StrUtil2.getOrDefault(config.getPackageName(), PACKAGE_NAME));
        // 创建类，指定类名称
        ClassOrInterfaceDeclaration cd = cu.addClass(StrUtil2.getOrDefault(config.getClassName(), CLASS_NAME));
        // 添加类注释
        if (StrUtil2.isNotBlank(config.getJavadoc())) {
            JavadocComment javadocComment = new JavadocComment(config.getJavadoc());
            cd.setComment(javadocComment);
        }
        // 添加类注解
        boolean useLombok = config.getUseLombok();
        if (useLombok) {
            cu.addImport("lombok.Data");
            cd.addMarkerAnnotation("Data");
        }
        // 添加类属性
        List<EntityPropertyConfigBO> propertyList = config.getPropertyList();
        if (CollectionUtil.isNotEmpty(propertyList)) {
            propertyList.forEach(property -> {
                FieldDeclaration field = cd.addField(property.getDataType(), property.getName(), Modifier.Keyword.PRIVATE);
                if (StrUtil2.isNotBlank(property.getPkgName())) {
                    cu.addImport(property.getPkgName());
                }
                if (!useLombok) {
                    field.createSetter();
                    field.createGetter();
                }
                if (StrUtil2.isNotBlank(property.getRemark())) {
                    JavadocComment fieldDoc = new JavadocComment(property.getRemark());
                    field.setComment(fieldDoc);
                }
                if (StrUtil2.isNotBlank(property.getJsonIgnore())) {
                    field.addAnnotation(property.getJsonIgnore());
                    cu.addImport("com.fasterxml.jackson.annotation.JsonIgnore");
                }
                if (StrUtil2.isNotBlank(property.getJsonFormat())) {
                    field.addAnnotation(property.getJsonFormat());
                    cu.addImport("com.fasterxml.jackson.annotation.JsonFormat");
                }
                if (StrUtil2.isNotBlank(property.getExcelExport())) {
                    field.addAnnotation(property.getExcelExport());
                }
            });
        }
        return cu.toString();
    }

}